package com.atguigu.tingshu.album.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import co.elastic.clients.elasticsearch.ElasticsearchClient;
import com.atguigu.tingshu.album.mapper.AlbumInfoMapper;
import com.atguigu.tingshu.album.mapper.AlbumStatMapper;
import com.atguigu.tingshu.album.mapper.TrackInfoMapper;
import com.atguigu.tingshu.album.service.AlbumAttributeValueService;
import com.atguigu.tingshu.album.service.AlbumInfoService;
import com.atguigu.tingshu.album.service.AuditService;
import com.atguigu.tingshu.common.execption.GuiguException;
import com.atguigu.tingshu.common.rabbit.constant.MqConst;
import com.atguigu.tingshu.common.rabbit.service.RabbitService;
import com.atguigu.tingshu.model.album.AlbumAttributeValue;
import com.atguigu.tingshu.model.album.AlbumInfo;
import com.atguigu.tingshu.model.album.AlbumStat;
import com.atguigu.tingshu.model.album.TrackInfo;
import com.atguigu.tingshu.query.album.AlbumInfoQuery;
import com.atguigu.tingshu.vo.album.AlbumInfoVo;
import com.atguigu.tingshu.vo.album.AlbumListVo;
import com.atguigu.tingshu.vo.album.AlbumStatVo;
import com.atguigu.tingshu.vo.album.TrackStatMqVo;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.stream.Collectors;

import static com.atguigu.tingshu.common.constant.SystemConstant.*;

@Slf4j
@Service
@SuppressWarnings({"all"})
public class AlbumInfoServiceImpl extends ServiceImpl<AlbumInfoMapper, AlbumInfo> implements AlbumInfoService {


    @Autowired
    private AlbumStatMapper albumStatMapper;

    @Autowired
    private AlbumAttributeValueService albumAttributeValueService;

    @Autowired
    private TrackInfoMapper trackInfoMapper;

    @Autowired
    private RabbitService rabbitmqService;

    @Autowired
    private AuditService auditService;

    @Autowired
    private ElasticsearchClient elasticsearchClient;


    /**
     * 新增加专辑
     *
     * @param albumInfoVo
     * @param userId
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveAlbumInfo(AlbumInfoVo albumInfoVo, Long userId) {

        AlbumInfo info = BeanUtil.copyProperties(albumInfoVo, AlbumInfo.class);
        info.setUserId(userId);
        info.setTracksForFree(5);
        info.setStatus(TRACK_STATUS_REVIEWING);
        info.setUserId(userId);
        String text = info.getAlbumTitle() + info.getAlbumIntro();
        String result = auditService.auditText(text);
        if ("pass".equals(result)) {
            info.setStatus(ALBUM_STATUS_PASS);
            rabbitmqService.sendMessage(MqConst.EXCHANGE_ALBUM, MqConst.ROUTING_ALBUM_UPPER, info.getId());
        } else if ("block".equals(result)) {
            info.setStatus(ALBUM_STATUS_NO_PASS);
        } else if ("review".equals(result)) {
            info.setStatus(ALBUM_STATUS_REVIEW);
        }
        //审核通过发送mq信息向搜索服务
        //保存专辑信息
        baseMapper.insert(info);

        //获取专辑id
        Long id = info.getId();
        // info里面还有一个属性值 使用工具类
        List<AlbumAttributeValue> albumAttributeValueVoList = info.getAlbumAttributeValueVoList();
        if (CollUtil.isEmpty(albumAttributeValueVoList)) {
            throw new GuiguException(500, "专辑属性为空");
        }
        //使用steam流的方式获取属性值
        List<AlbumAttributeValue> attributeValueList = albumAttributeValueVoList.stream().map(vo -> {
            AlbumAttributeValue attributeValue = BeanUtil.copyProperties(vo, AlbumAttributeValue.class);
            attributeValue.setAlbumId(id);
            return attributeValue;
        }).collect(Collectors.toList());

        albumAttributeValueService.saveBatch(attributeValueList);
        //为四个属性赋值
        this.saveAlbumStateInfo(id, ALBUM_STAT_PLAY, 0);
        this.saveAlbumStateInfo(id, ALBUM_STAT_SUBSCRIBE, 0);
        this.saveAlbumStateInfo(id, ALBUM_STAT_BUY, 0);
        this.saveAlbumStateInfo(id, ALBUM_STAT_COMMENT, 0);
    }

    @Override
    public void saveAlbumStateInfo(Long albumId, String statType, Integer statNum) {
        AlbumStat albumStat = new AlbumStat();
        albumStat.setAlbumId(albumId);
        albumStat.setStatType(statType);
        albumStat.setStatNum(statNum);
        albumStatMapper.insert(albumStat);
    }

    @Override
    public Page<AlbumListVo> findUserAlbumPage(Page<AlbumListVo> albumListVoPage, AlbumInfoQuery query) {
        Page<AlbumListVo> page = baseMapper.findUserAlbumPage(albumListVoPage, query);
        return page;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void removeAlbumInfo(Long id) {

        Long count = trackInfoMapper.selectCount(
                new LambdaQueryWrapper<TrackInfo>().eq(TrackInfo::getAlbumId, id));
        if (count > 0) {
            throw new GuiguException(500, "专辑中包含声音，请先删除专辑中的声音");
        }
        //删除专辑信息
        baseMapper.deleteById(id);
        //删除专辑四个属性
        albumStatMapper.delete(new LambdaQueryWrapper<AlbumStat>().eq(AlbumStat::getAlbumId, id));
        //删除专辑关联中间表
        albumAttributeValueService.remove(new LambdaQueryWrapper<AlbumAttributeValue>().eq(AlbumAttributeValue::getAlbumId, id));
    }

    @Override
    public AlbumInfo getAlbumInfo(Long id) {
        AlbumInfo albumInfo = baseMapper.selectById(id);
        List<AlbumAttributeValue> albumAttributeValueList = albumAttributeValueService.list(
                new LambdaQueryWrapper<AlbumAttributeValue>().eq(AlbumAttributeValue::getAlbumId, id));
        if (CollUtil.isNotEmpty(albumAttributeValueList)) {
            albumInfo.setAlbumAttributeValueVoList(albumAttributeValueList);
        }
        return albumInfo;
    }

    /**
     * 修改专辑列表
     *
     * @param id
     * @param albumInfoVo
     */
    @Override
    public void updateAlbumInfo(Long id, AlbumInfoVo albumInfoVo) {
        //修改专辑的信息
        AlbumInfo albumInfo = BeanUtil.copyProperties(albumInfoVo, AlbumInfo.class);
        //进行文本审核
        String text = albumInfoVo.getAlbumTitle() + albumInfoVo.getAlbumIntro();
        String resultText = auditService.auditText(text);
        if ("pass".equals(resultText)) {
            albumInfo.setStatus(ALBUM_STATUS_PASS);
            rabbitmqService.sendMessage(MqConst.EXCHANGE_ALBUM, MqConst.ROUTING_ALBUM_UPPER, albumInfo.getId());
        } else if ("block".equals(resultText)) {
            albumInfo.setStatus(ALBUM_STATUS_NO_PASS);
        } else if ("review".equals(resultText)) {
            albumInfo.setStatus(ALBUM_STATUS_REVIEW);
        }
        //如果通过则进行修改专辑的信息以及其关联的属性
        albumInfo.setId(id);
        baseMapper.updateById(albumInfo);
        //修改关联的表
        albumAttributeValueService.remove(
                new LambdaQueryWrapper<AlbumAttributeValue>().eq(AlbumAttributeValue::getAlbumId, id));


        List<AlbumAttributeValue> albumAttributeValueVoList = albumInfo.getAlbumAttributeValueVoList();
        List<AlbumAttributeValue> attributeValueList = albumAttributeValueVoList.stream().map(vo -> {
            AlbumAttributeValue attributeValue = BeanUtil.copyProperties(vo, AlbumAttributeValue.class);
            attributeValue.setAlbumId(id);

            return attributeValue;
        }).collect(Collectors.toList());
        albumAttributeValueService.saveBatch(attributeValueList);
    }

    @Override
    public List<AlbumInfo> findUserAllAlbumList(Long userId) {
        LambdaQueryWrapper<AlbumInfo> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(AlbumInfo::getUserId, userId);
        queryWrapper.orderByDesc(AlbumInfo::getCreateTime);
        queryWrapper.last("limit 200");
        return baseMapper.selectList(queryWrapper);
    }

    /**
     * 获取专辑统计信息
     *
     * @param albumId
     * @return
     */
    @Override
    public AlbumStatVo getAlbumStatVo(Long albumId) {
        AlbumStatVo albumStatVo = albumStatMapper.getAlbumStatVo(albumId);
        return albumStatVo;
    }


    /**
     * 更新数据库里面的专辑相关的统计信息
     *
     * @param trackStatMqVo
     */

    private final static String ALBUMINFO_INDEX = "albuminfo";

    @Override
    public void updateTrackStat(TrackStatMqVo trackStatMqVo) {

        //1.更新数据库的信息
        Long albumId = trackStatMqVo.getAlbumId();
        String statType = trackStatMqVo.getStatType();
        Integer count = trackStatMqVo.getCount();
        //2.更新所属专辑（播放、评论）统计信息
        if (TRACK_STAT_PLAY.equals(statType)) {
            albumStatMapper.update(
                    null,
                    new LambdaUpdateWrapper<AlbumStat>()
                            .eq(AlbumStat::getAlbumId, albumId)
                            .eq(AlbumStat::getStatType, ALBUM_STAT_PLAY)
                            .setSql("stat_num = stat_num + " + count)
            );
        }//todo 2.更新es里面的信息

    }
}
